package com.cxria.problem.service.impl

import com.cxria.problem.dao.UserDao
import com.cxria.problem.dto.PasswordDto
import com.cxria.problem.dto.Status
import com.cxria.problem.entity.User
import com.cxria.problem.enums.StatusCodeEnum
import com.cxria.problem.enums.StatusMsgEnum
import com.cxria.problem.service.UserService
import com.cxria.problem.utils.ErrorUtils
import org.springframework.beans.factory.annotation.Autowired
import org.springframework.cache.annotation.Cacheable
import org.springframework.security.core.context.SecurityContextHolder
import org.springframework.security.core.userdetails.UserDetails
import org.springframework.security.core.userdetails.UserDetailsService
import org.springframework.security.core.userdetails.UsernameNotFoundException
import org.springframework.security.crypto.password.PasswordEncoder
import org.springframework.stereotype.Service
import org.springframework.transaction.annotation.Transactional

@Service
class UserServiceImpl implements UserService, UserDetailsService {

	@Autowired
	UserDao userDao

	@Autowired
    PasswordEncoder passwordHelper

	@Autowired
    ErrorUtils errorUtils

	@Override
	@Cacheable(value='User', key="'userId'")
	List<User> findAll() {
		return userDao.findAll()
	}

	@Override
    User getByUsername(String username) {
		return userDao.findOne(null, username)
	}

	@Override
	User getById(Integer userId) {
		return userDao.findOne(userId, null)
	}

	@Override
	void add(User user) {

	}

	@Override
	void delete(long id) {

	}

	@Override
	@Transactional
	void updatePassword(PasswordDto passwordDto){
		User user = getCurrentUser()
		if(passwordHelper.matches(passwordDto.oldPassword, user.password)){
			String lastPassword = passwordHelper.encode(passwordDto.newPassword)
			user.setPassword(lastPassword)
			userDao.update(user)
		} else {
			def status = new Status(Status.ERROR, StatusCodeEnum.USER_INCORRECT_CREDENTIALS_ERROR, StatusMsgEnum.USER_INCORRECT_CREDENTIALS_ERROR)
			errorUtils.throwException(status)
		}
	}

	@Override
    UserDetails loadUserByUsername(String username){
		User user = getByUsername(username)
		if(null == user){
			throw new UsernameNotFoundException('username not found')
		}
		user
	}

	@Override
    User getCurrentUser(){
		SecurityContextHolder.context.authentication.principal
	}

}
